using System;

namespace SharpObjects.Utils
{
    public class TypedAccessor
    {
        protected object m_obj;

        public TypedAccessor(object obj)
        {
            m_obj = obj;
        }

        public object GetObject { get { return m_obj; } }

        public bool Boolean() { return TypedAccessor.GetBoolean(m_obj); }
        public bool Boolean(bool DefaultValue) { return TypedAccessor.GetBoolean(m_obj, DefaultValue); }

        public DateTime DateTime() { return TypedAccessor.GetDateTime(m_obj); }
        public DateTime DateTime(DateTime DefaultValue) { return TypedAccessor.GetDateTime(m_obj, DefaultValue); }

        public int Integer() { return TypedAccessor.GetInteger(m_obj); }
        public int Integer(int DefaultValue) { return TypedAccessor.GetInteger(m_obj, DefaultValue); }

        public long Long() { return TypedAccessor.GetLong(m_obj); }
        public long Long(long DefaultValue) { return TypedAccessor.GetLong(m_obj, DefaultValue); }

        public double Double() { return TypedAccessor.GetDouble(m_obj); }
        public double Double(double DefaultValue) { return TypedAccessor.GetDouble(m_obj, DefaultValue); }

        public decimal Decimal() { return TypedAccessor.GetDecimal(m_obj); }
        public decimal Decimal(decimal DefaultValue) { return TypedAccessor.GetDecimal(m_obj, DefaultValue); }

        public string String() { return TypedAccessor.GetString(m_obj); }
        public string String(string DefaultValue) { return TypedAccessor.GetString(m_obj, DefaultValue); }


        public static bool GetBoolean(object obj)
        {
            return GetBoolean(false);
        }

        public static bool GetBoolean(object obj, bool DefaultValue)
        {
            try
            {
                if (obj == null)
                {
                    return DefaultValue;
                }
                else if (obj is Boolean)
                {
                    return (Boolean)obj;
                }
                else if (obj is Byte || obj is Int16 || obj is Int32 || obj is Int64 || obj is Double)
                {
                    Double val = (Double)obj;
                    return val != 0;
                }
                else if (obj is String || obj is Char)
                {
                    string sValue;

                    if (obj is String)
                    {
                        sValue = obj.ToString().Trim();
                    }
                    else
                    {
                        sValue = new String((Char)obj, 1);
                    }

                    if (sValue == "0")
                    {
                        return false;
                    }
                    else if (sValue == "1")
                    {
                        return true;
                    }
                    else if (sValue.ToUpper() == "Y" || sValue.ToUpper() == "YES")
                    {
                        return true;
                    }
                    else if (sValue.ToUpper() == "N" || sValue.ToUpper() == "NO")
                    {
                        return false;
                    }
                    else if (sValue.ToUpper() == "T" || sValue.ToUpper() == "TRUE")
                    {
                        return true;
                    }
                    else if (sValue.ToUpper() == "F" || sValue.ToUpper() == "FALSE")
                    {
                        return false;
                    }
                    else
                    {
                        return Convert.ToBoolean(sValue);
                    }
                }
                else
                {
                    return Convert.ToBoolean(obj);
                }
            }
            catch
            {
                return DefaultValue;
            }
        }

        public static DateTime GetDateTime(object obj)
        {
            if (obj == null)
            {
                throw new NullReferenceException("Object being converted to DateTime is null");
            }
            else
            {
                return Convert.ToDateTime(obj);
            }
        }

        public static DateTime GetDateTime(object obj, DateTime DefaultValue)
        {
            if (obj == null)
            {
                return DefaultValue;
            }
            else
            {
                try
                {
                    return Convert.ToDateTime(obj);
                }
                catch
                {
                    return DefaultValue;
                }
            }
        }

        public static double GetDouble(object obj)
        {
            if (obj == null)
            {
                throw new NullReferenceException("Object being converted to Double is null");
            }

            if (obj is Double)
            {
                return (Double)obj;
            }
            else
            {
                string sValue = obj.ToString().Trim();
                return Convert.ToDouble(sValue);
            }
        }

        public static double GetDouble(object obj, double DefaultValue)
        {
            if (obj == null)
            {
                return DefaultValue;
            }

            return GetDouble(obj);
        }

        public static decimal GetDecimal(object obj)
        {
            if (obj == null)
            {
                throw new NullReferenceException("Object being converted to Decimal is null");
            }

            if (obj is Decimal)
            {
                return (Decimal)obj;
            }
            else
            {
                string sValue = obj.ToString().Trim();
                return Convert.ToDecimal(sValue);
            }
        }

        public static decimal GetDecimal(object obj, decimal DefaultValue)
        {
            if (obj == null)
            {
                return DefaultValue;
            }

            return GetDecimal(obj);
        }

        public static int GetInteger(object obj)
        {
            if (obj == null)
            {
                throw new NullReferenceException("Object being converted to Int32 is null");
            }

            if (obj is Int32)
            {
                return (Int32)obj;
            }
            else if (obj is byte)
            {
                return (Int32)obj;
            }
            else if (obj is short)
            {
                return (Int32)obj;
            }
            else if (obj is decimal)
            {
                decimal val = (decimal)obj;
                return Convert.ToInt32(val);
            }
            else if (obj is double)
            {
                double val = (double)obj;
                return Convert.ToInt32(val);
            }
            else if (obj is float)
            {
                float val = (float)obj;
                return Convert.ToInt32(val);
            }
            else
            {
                string sValue = obj.ToString().Trim();
                return Convert.ToInt32(sValue);
            }
        }

        public static int GetInteger(object obj, int DefaultValue)
        {
            if (obj == null)
            {
                return DefaultValue;
            }

            return GetInteger(obj);
        }

        public static long GetLong(object obj)
        {
            if (obj == null)
            {
                throw new NullReferenceException("Object being converted to Long is null");
            }

            if (obj is Int32)
            {
                return (Int64)obj;
            }
            else if (obj is byte)
            {
                return (Int64)obj;
            }
            else if (obj is short)
            {
                return (Int64)obj;
            }
            else if (obj is Int64)
            {
                return (Int64)obj;
            }
            else if (obj is decimal)
            {
                decimal val = (decimal)obj;
                return Convert.ToInt64(val);
            }
            else if (obj is double)
            {
                double val = (double)obj;
                return Convert.ToInt64(val);
            }
            else if (obj is float)
            {
                float val = (float)obj;
                return Convert.ToInt64(val);
            }
            else
            {
                string sValue = obj.ToString().Trim();
                return Convert.ToInt64(sValue);
            }
        }

        public static long GetLong(object obj, long DefaultValue)
        {
            if (obj == null)
            {
                return DefaultValue;
            }

            return GetLong(obj);
        }

        public static string GetString(object obj)
        {
            if (obj == null)
            {
                throw new NullReferenceException("Object being converted to String is null");
            }
            return obj.ToString();
        }

        public static string GetString(object obj, string DefaultValue)
        {
            if (obj == null)
            {
                return DefaultValue;
            }
            return GetString(obj);
        }


    }
}